<script id="vertex-shader" type="x-shader/x-vertex">
    precision mediump float;

    attribute vec4 vPosition;
    uniform mat4 modelViewMatrix;
    uniform mat4 normalMatrix;
    uniform mat4 projectMatrix;
    uniform vec4 lightPosition;
    attribute vec4 aProduct;
    attribute vec4 dProduct;
    attribute vec4 sProduct;
    attribute vec4 vNormal;
    attribute float shininess;
    varying vec4 aP, dP, sP;
    varying float shine;
    varying vec3 L, V;

    attribute vec2 vTexCoord;
    varying vec2 fTexCoord;
    attribute vec2 vNormalCoord;
    varying vec2 fNormalCoord;

    attribute vec3 vTan;

    void main() {
        gl_Position = projectMatrix * modelViewMatrix * vPosition; 
        
        vec3 pos = (modelViewMatrix * vPosition).xyz;
        vec3 light = (modelViewMatrix * lightPosition).xyz;
        vec3 eyeLight = normalize(light);
        vec3 N = normalize((normalMatrix * vNormal).xyz);
        vec4 vTan4;
        vTan4.xyz = vTan;
        vTan4.a = 0.0;
        vec3 T = normalize(normalMatrix * vTan4).xyz;
        vec3 B = cross(N, T);


        L.x = dot(T, eyeLight);
        L.y = dot(B, eyeLight);
        L.z = dot(N, eyeLight);
        L = normalize(L);

        vec3 eye = normalize(-pos);
        vec3 V;
        V.x = dot(T, eye);
        V.y = dot(B, eye);
        V.z = dot(N, eye);
        V = normalize(V);


        aP = aProduct;
        dP = dProduct;
        sP = sProduct;
        shine = shininess;

        fTexCoord = vTexCoord;
        fNormalCoord = vNormalCoord;
    }
</script>

<script id="fragment-shader" type="x-shader/x-fragment">
    precision mediump float;
    varying vec2 fTexCoord;
    varying vec2 fNormalCoord;
    uniform sampler2D texMap;
    uniform sampler2D normalMap;
    varying vec4 aP, dP, sP;
    varying float shine;
    varying vec3 L, V;

    void main(){
        vec4 N4 = texture2D(normalMap, fNormalCoord);
        vec3 N = normalize(2.0*N4.xyz-1.0);
        vec3 LL = normalize(L);
        vec3 H = normalize(LL+V);
        vec4 ambient = aP;
        float Kd = max(dot(LL, N), 0.0);
        vec4 diffuse = Kd * dP;

        float Ks = pow(max(dot(N, H), 0.0), shine);
        vec4 specular = Ks * sP;
        if (dot(LL,N)<0.0) {
            specular = vec4(0.0,0.0,0.0,1.0);
        }

        vec4 fColor = ambient + diffuse + specular;
        fColor.a = 1.0;
        gl_FragColor = fColor * texture2D(texMap, fTexCoord);
    }
</script>
<script src="js/jquery-3.5.1.min.js"></script>
<script type="text/javascript" src="js/Common/webgl-utils.js"></script>
<script type="text/javascript" src="js/Common/initShaders.js"></script>
<script type="text/javascript" src="js/Common/MV.js"></script>
<script type="text/javascript" src="Experiment/Experiment4/snowmen.js"></script>
<canvas id="gl-canvas" width="512" height="512">
    Oooooops!
</canvas>
<center><button onclick="lightMove()" style="height:50px; width:400px; font-size:24px;">光源移动/暂停</button></center>